import datetime
from typing import List, Union, Literal, Dict
from pydantic import Field, BaseModel
from package.fastapi.schema import Page, BatchId, Request, Cron, uuid7_hex, DatabaseOption

# collector_task
# 动态认证token获取配置
class _TokenSettings(BaseModel):
    token_in: Literal['headers', 'body'] = Field(None, title='token所在')
    token_in_field: str = Field(None, title='需要获取的token 字段名')
    token_set: Literal['headers', 'params'] = Field(..., title='token所在')
    token_set_field: str = Field(..., title='token名')
    token_prefix: str = Field(None, title='token前缀', description='例如: Beare xxx')


class _DynamicAuth(BaseModel):
    """动态认证方式"""
    request: Request = Field(..., title='请求')
    token_settings: _TokenSettings = Field(..., title='动态认证配置')


# 请求动态认证
class _AuthRequest(Request):
    """请求"""
    dynamic_auth: _DynamicAuth = Field(None, title='动态认证')


class _APIOption(BaseModel):
    """api采集 字段选择"""
    field: str = Field(None, title='采集字段')


class _APICollector(_AuthRequest):
    """API采集"""
    option: _APIOption = Field(..., title='选项配置')


class _DatabaseCollector(BaseModel):
    """数据库 采集"""
    option: DatabaseOption = Field(..., title='数据库连接')
    sql: str = Field(..., title='查询语句')


class _CollectorExtra(BaseModel):
    as_list: bool = Field(True, title='列表是否拆分')


# logstash配置
class _KafkaOption(BaseModel):
    """kafka logstash配置"""
    topics: List[str] = Field(..., title='采集的topic')
    group_id: str = Field('kafka_collector', title='采集消费者组')
    auto_offset_reset: str = Field('latest', title='偏移')


class _HttpOption(BaseModel):
    """apiserver logstash配置"""
    headers: List[str] = Field(..., title='请求头')


# 数据源配置
class EditSource(BaseModel):
    """修改记录"""
    name: str = Field(..., title='数据源名称')
    description: str = Field('', title='数据源描述')
    category: str = Field('', title='数据源描述')
    host: str = Field(None, title='数据源IP')
    port: int = Field(None, title='数据源端口')
    configure: Union[_KafkaOption, _HttpOption, Dict] = Field(None, title='额外配置')


class CreateSource(EditSource):
    """创建记录"""
    category: str = Field(None, title='数据源类型')


class SourceOut(CreateSource):
    """返回数据不返回密码"""
    id: str = Field(..., title='记录ID')
    enabled: bool = Field(..., title='启用与禁用')
    created_at: datetime.datetime = Field(None, title='')

    class Config:
        orm_mode = True
        extra = 'allow'
        json_encoders = {datetime.datetime: lambda dt: int(dt.timestamp() * 1000)}


class PageSources(Page):
    """获取页码条目"""
    data: List[SourceOut] = Field(..., title='')


class VerifyCollector(BaseModel):
    """单条验证"""
    category: str = Field(None, title='数据源类型')
    configure: Union[_DatabaseCollector, _APICollector] = Field(..., title='数据采集配置')


class EditCollector(Cron):
    name: str = Field(None, title='名称')
    description: str = Field('', title='描述')
    configure: Union[_APICollector, _DatabaseCollector] = Field(None, title='采集数据配置')
    as_list: bool = Field(True, title='列表数据按单条发送')


class CreateCollector(EditCollector):
    category: str = Field(None, title='数据源类型') 


class EnableCollector(BaseModel):
    enabled: bool = Field(..., title='状态')


class CollectorOut(CreateCollector):
    id: str = Field(..., title='ID')
    created_at: datetime.datetime = Field(None, title='')

    class Config:
        orm_mode = True
        json_encoders = {datetime.datetime: lambda dt: int(dt.timestamp() * 1000)}
